﻿#define _CRT_SECURE_NO_WARNINGS

#include <iostream>
using namespace std;

//double Divide(int a, int b)
//{
//	try
//	{
//		// 当b == 0时抛出异常
//		if (b == 0)
//		{
//			string s("Divide by zero condition!");
//			throw s; // 抛出异常
//		}
//		else
//		{
//			return a * 1.0 / b;
//		}
//	}
//	catch (string errid) // 捕获的类型匹配
//	{
//		cout << "Divide(): " << errid << endl;
//	}
//
//	return 0;
//}
//
//void func()
//{
//	int a, b; 
//	cin >> a >> b;
//	cout << Divide(a, b) << endl;
//	cout << "hello world" << endl;
//}

//int main()
//{
//	try
//	{
//		func();
//	}
//	catch(string& s)
//	{
//		cout << "main(): " << s << endl;
//	}
//
//	return 0;
//}


// 一般⼤型项⽬程序才会使用异常，下面我们模拟设计一个服务的几个模块
// 每个模块的继承都是Exception的派生类，每个模块可以添加自己的数据
// 最后捕获时，我们捕获基类就可以
//class Exception
//{
//public:
//	Exception(const string& errmsg, int id)
//		:_errmsg(errmsg)
//		, _id(id)
//	{ }
//	virtual string what() const
//	{
//		return _errmsg;
//	}
//	int getid() const
//	{
//		return _id;
//	}
//protected:
//	string _errmsg;
//	int _id;
//};
//
//class CacheException : public Exception
//{
//public:
//	CacheException(const string& errmsg, int id)
//		:Exception(errmsg, id)
//	{ }
//	virtual string what() const
//	{
//		string str = "CacheException:";
//		str += _errmsg;
//		return str;
//	}
//};
//
//class HttpException : public Exception
//{
//public:
//	HttpException(const string& errmsg, int id, const string& type)
//		//:Exception(errmsg, id)
//		: _type(type)
//	{ }
//	virtual string what() const
//	{
//		string str = "HttpException:";
//		str += _type;
//		str += ":";
//		//str += _errmsg;
//		return str;
//	}
//private:
//	const string _type;
//};

//void CacheMgr()
//{
//	if (rand() % 5 == 0)
//	{
//		throw CacheException("权限不足", 100);
//	}
//	else if (rand() % 6 == 0)
//	{
//		throw CacheException("数据不存在", 101);
//	}
//	else
//	{
//		cout << "CacheMgr 调用成功" << endl;
//	}
//}
//
//void HttpServer()
//{
//	if (rand() % 3 == 0)
//	{
//		throw HttpException("请求资源不存在", 100, "get");
//	}
//	else if (rand() % 4 == 0)
//	{
//		throw HttpException("权限不足", 101, "post");
//	}
//	else
//	{
//		cout << "HttpServer调用成功" << endl;
//	}
//	CacheMgr();
//}
// 
//int main()
//{
//	srand(time(0));
//	int cnt = 3;
//	while (cnt)
//	{
//		cnt--;
//		try
//		{
//			HttpServer();
//		}
//		catch (const Exception& e) // 这⾥捕获基类，基类对象和派⽣类对象都可以被捕获
//		{
//			cout << e.what() << endl; // 多态
//		}
//		catch (...)
//		{
//			cout << "未知异常" << endl;
//		}
//
//		cout << endl;
//	}
//	return 0;
//}
//
//
//catch (...)
//{
//	cout << "未知异常" << endl;
//}
//#include <ctime>

class Exception
{
public:
	Exception(const string& errmsg, int id)
		:_errmsg(errmsg)
		, _id(id)
	{ }
	virtual string what() const
	{
		return _errmsg;
	}
	int getid() const
	{
		return _id;
	}
protected:
	string _errmsg;
	int _id;
};

class HttpException : public Exception
{
public:
	HttpException(const string& errmsg, int id, const string& type)
		:Exception(errmsg, id)
		, _type(type)
	{ }
	virtual string what() const
	{
		string str = "HttpException:";
		str += _type;
		str += ":";
		str += _errmsg;
		return str;
	}
private:
	const string _type;
};


void _SeedMsg(const string& s)
{
	if (rand() % 2 == 0)
	{
		throw HttpException("网络不稳定，发送失败", 102, "put");
	}
	else if (rand() % 7 == 0)
	{
		throw HttpException("你已不是对方的好友，发送失败", 103, "put");
	}
	else
	{
		cout << "发送成功" << endl;
	}
}

void SendMsg(const string& s)
{
	// 发送消息失败，则再重试3次
	for (size_t i = 0; i < 4; i++)
	{
		try
		{
			_SeedMsg(s); // 出现 102 号错误，尝试重连
			break;
		}
		catch (const Exception& e)
		{
			// 捕获异常，if中是102
			// 捕获异常，else中不是102号错误，则将异常重新抛出
			if (e.getid() == 102) // 判断错误码是不是 102
			{
				// 重试三次以后否失败了，则说明网络太差了，重新抛出异常
				if (i == 3) throw; // 捕获到什么异常就抛出什么
				cout << "开始第" << i + 1 << "重试" << endl;
			}
			else
			{
				throw;
			}
		}
	}
}

//int main()
//{
//	srand(time(0));
//	string str = "中！";
//	int cnt = 5;
//	while (cnt)
//	{
//		cnt--;
//		try
//		{
//			SendMsg(str);
//		}
//		catch (const Exception& e)
//		{
//			cout << e.what() << endl;
//		}
//		catch (...)
//		{
//			cout << "未知异常" << endl;
//		}
//
//		cout << endl;
//	}
//
//	return 0;
//}

double Divide(int a, int b)
{
	// 当b == 0时抛出异常
	if (b == 0)
	{
		string s("Divide by zero condition!");
		throw s; // 抛出异常
	}

	return a * 1.0 / b;
}

void func()
{
	int* arr = new int[10];
	try
	{
		int a, b;
		cin >> a >> b;
		cout << Divide(a, b) << endl;
	}
	catch (...)
	{
		// 捕获所有异常，释放内存
		cout << "delete[] arr" << endl;
		delete[] arr;

		throw; // 将异常抛给上一个调用处理
	}
	cout << "delete[] arr" << endl;
	delete[] arr;
}

//int main()
//{
//	try
//	{
//		func();
//	}
//	catch (string& s)
//	{
//		cout << "main(): " << s << endl;
//	}
//
//	return 0;
//}
#include <vector>

int main()
{
	vector<int> v;
	cout << noexcept(v.size()) << endl;
	cout << noexcept(v.push_back(1)) << endl;

	return 0;
}